package com.zts.base.exception;

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

/**
 * Created by Zhangkh on 2017/6/1.
 */
public class Exceptions {
    private static Logger logger = LoggerFactory.getLogger(Exceptions.class);

    private static String getId(Throwable throwable) {
        return throwable instanceof CommonException ? ((CommonException)throwable).getId() : "-";
    }

    public static void catching(Throwable throwable) {
        catching(throwable, false);
    }

    public static void catching(Throwable throwable, boolean printStacktrace) {
        if (!printStacktrace) {
            logger.warn("Catching exception {}[{}]: {}", throwable.getClass(), getId(throwable), throwable.getLocalizedMessage());
        } else {
            logger.warn("Catching exception {}[{}]: {}", throwable.getClass(), getId(throwable), throwable);
        }
    }

    public static CommonException wrap(Throwable throwable) {
        return wrap(throwable, new ServiceException());
    }

    public static <T extends Throwable> T wrap(Throwable cause, T ex) {
        logger.warn("Wrapping exception {} to {}[{}]", cause.getClass(), ex.getClass(), getId(ex));

        ex.initCause(cause);
        return ex;
    }

    public static <T extends CommonException> CommonException wrap(Throwable cause, T ex) {
        if (CommonException.class.isAssignableFrom(cause.getClass())) {
            return (CommonException)cause;
        }

        logger.warn("Wrapping exception {} to {}[{}]", cause.getClass(), ex.getClass(), getId(ex));

        ex.initCause(cause);
        return ex;
    }

    @SuppressWarnings("unchecked")
    public static <T extends Throwable> void propagateIfInstanceOf(Throwable ex, Class<T> clazz) throws T {
        if (clazz.isAssignableFrom(ex.getClass())) {
            throw (T)ex;
        }
    }
}